package com.fishleap.service;

import com.fishleap.codec.NettyDecoder;
import com.fishleap.codec.NettyEncoder;
import com.fishleap.dto.RpcRequest;
import com.fishleap.dto.RpcResponse;
import com.fishleap.enumeration.RpcResponseCode;
import com.fishleap.handler.UserServiceHandler;
import com.fishleap.registry.ServiceRegistry;
import com.fishleap.registry.ZkServiceRegistry;
import com.fishleap.serialize.kyro.KryoSerializer;
import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelPipeline;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import io.netty.channel.socket.nio.NioSocketChannel;
import org.springframework.stereotype.Service;

import java.net.InetSocketAddress;

/**
 * @author zlg
 */
@Service
public class UserServiceImpl implements IUserService {

    //将来客户单要远程调用的方法
    @Override
    public RpcResponse<String> sayHello(String msg) {

        System.out.println("从客户端接受的数据 : "+msg);
        if (msg != null) {
            return RpcResponse.success("从服务器 127.0.0.1:8888 接受的数据" + msg, "");
        }else {
            return RpcResponse.fail(RpcResponseCode.FAIL);
        }

    }

    public String sayHelloString(String msg) {
        System.out.println("客户端发送数据 : "+msg);
        return "服务器返回数据 : "+msg;
    }



    //创建一个方法启动服务器
    public static void startServer(String ip, int port) throws InterruptedException {

        //1.创建两个线程池对象
        NioEventLoopGroup bossGroup = new NioEventLoopGroup();
        NioEventLoopGroup workGroup = new NioEventLoopGroup();

        //2.创建服务端的启动引导对象
        ServerBootstrap serverBootstrap = new ServerBootstrap();

        //3.配置启动引导对象
        serverBootstrap.group(bossGroup, workGroup)
            //通道对象:NioServerSocketChannel  监听对象:NioSocketChannel
            .channel(NioServerSocketChannel.class)
            .childHandler(new ChannelInitializer<NioSocketChannel>() {
                @Override
                protected void initChannel(NioSocketChannel nioSocketChannel) throws Exception {
                    ChannelPipeline pipeline = nioSocketChannel.pipeline();
//                    pipeline.addLast(new StringEncoder());
//                    pipeline.addLast(new StringDecoder());
                    pipeline.addLast(new NettyDecoder(new KryoSerializer(), RpcRequest.class));
                    pipeline.addLast(new NettyEncoder(new KryoSerializer(), RpcResponse.class));
                    //把自定义的ChannelHander添加到通道中
                    pipeline.addLast(new UserServiceHandler());
                }
            });

        //4.绑定端口
        serverBootstrap.bind(ip, port).sync();

        //5.使用Zookeeper进行服务注册
        ServiceRegistry serviceRegistry = new ZkServiceRegistry();
        // 获取接口名称字节码对象的全限定类名
        serviceRegistry.registryService(IUserService.class.getCanonicalName(),
                new InetSocketAddress(ip, port));

    }

}
